<template>
	<!-- 发布讨论帖的字体内容修改 -->
	<view class="content-editor">
		<view class="editor-box">
			<slot name="header"></slot>
			<view class="editor-content">
				<editor id="editor" class="ql-container" :style="{height}"
					:placeholder="placeholder"
					:show-img-size="false"
					:show-img-toolbar="false"
					@focus="onEditorFocus"
					@blur="onEditorBlur"
					@input="onEditorInput"
					@ready="onEditorReady"></editor>
			</view>
			<slot name="footer"></slot>
			<view class="editor-tools flex-r ac">
				<view class="tools-list flex-r ac">
					<scroll-view scroll-x="true" class="scroll-view">
						<view class="list" @touchmove.stop @tap="format">
							<template v-for="(item, index) in tools">
								<image class="icon" :src="require('@/public/images/editor/'+item.icon+'.png')" mode="aspectFit" :key="index" 
									:data-index="index"
									:data-name="item.name"
									:data-value="item.value"
									:data-label="item.text"
									:class="{'active': currentTool.includes(item.name)}"
								></image>
							</template>
						</view>
					</scroll-view>
					<view class="mask"></view>
				</view>
				<view class="keyboard flex-r ac jc">
					<image class="icon" src="@/public/images/editor/jp.png" mode="aspectFit" v-if="!editorFocus"></image>
					<image class="icon" src="@/public/images/editor/sq.png" mode="aspectFit" v-if="editorFocus"></image>
				</view>
			</view>
		</view>
		<uni-popup ref="popup" :safe-area="false" type="bottom" class="popup-box" @maskClick="toggle(false)">
			<view class="popup-head flex-r ac">
				<text @tap="toggle(false)">取消</text>
				<text class="text-bold">{{popupInfo.label}}</text>
				<text class="color-blue" @tap="submitFormat">确定</text>
			</view>
			<view class="popup-view bottom-ios">
				<view class="font-size flex-c" v-if="popupInfo.name == 'fontSize'">
					<text class="text-primary">效果展示</text>
					<view class="display-area flex-r ac jc">
						<text :style="'font-size: '+popupInfo.value+'px;'">字号</text>
					</view>
					<view class="format-info text-primary">
						<text>字号：</text><text class="color-red text-bold">{{popupInfo.value}}</text>
					</view>
					<view class="slider-box flex-c">
						<slider class="slider" :value="popupInfo.value" min="10" max="100" @change="sliderChange" activeColor="#F23030" backgroundColor="#EDEDED" block-color="#F23030" block-size="24"></slider>
						<view class="slider-info text-primary flex-r ac jsb">
							<text>10</text>
							<text>100</text>
						</view>
					</view>
				</view>
				<view class="font-color flex-c" v-if="popupInfo.name == 'color'">
					<text class="text-primary">效果展示</text>
					<view class="display-area flex-r ac jc">
						<text :style="'color: '+popupInfo.value">字体颜色</text>
					</view>
					<view class="format-info flex-c">
						<text class="text-primary">字体颜色色卡</text>
						<view class="color-list flex-r" @tap="colorChange">
							<view class="color-item flex-r ac jc" v-for="(color, index) in colorList" :key="index" :data-color="color" :class="{'active': color == popupInfo.value}">
								<view class="color-card" :style="'background-color:'+color"></view>
							</view>
						</view>
					</view>
				</view>
				<view class="font-background flex-c" v-if="popupInfo.name == 'backgroundColor'">
					<text class="text-primary">效果展示</text>
					<view class="display-area flex-r ac jc">
						<text class="bgcolor" :style="'background-color: '+popupInfo.value+';color: '+popupInfo.color">字体背景色</text>
					</view>
					<view class="format-info flex-c">
						<text class="text-primary">字体背景色色卡</text>
						<view class="color-box flex-r ac jc">
							<text class="text-regular color-grey flex-r ac jc" :style="'background-color: '+popupInfo.value">{{popupInfo.value != '' ? '' : '无颜色'}}</text>
						</view>
						<view class="color-list flex-r" @tap="colorChange">
							<view class="color-item flex-r ac jc" v-for="(color, index) in colorList" :key="index" :data-color="color" :class="{'active': color == popupInfo.value}">
								<view class="color-card" :style="'background-color:'+color"></view>
							</view>
						</view>
					</view>
				</view>
			</view>
		</uni-popup>
	</view>
</template>

<script>
	/**
	 * ContentEditor 富文本编辑器
	 * @description 球吧发布方案、讨论贴等使用的富文本编辑器
	 * @property {String} type = [freeContent|content|topic|vote] 内容类型
	 *  @value freeContent 免费内容
	 *  @value content 付费内容，暂未启用
	 *  @value topic 话题贴内容
	 *  @value vote 投票贴内容
	 * @property {String} placeholder 默认占位内容
	 * @property {String} height 编辑器高度
	 * @event {Function} change 编辑内容变动
	 * @event {Function} focus 编辑器聚焦
	 * @event {Function} blur 编辑器失焦
	 * @example <ContentEditor type="freeContent"></ContentEditor>
	 */
	export default {
		name: "ContentEditor",
		emits: ['change', 'focus', 'blur'],
		props: {
			type: {
				type: String,
				default: 'freeContent'
			},
			placeholder: {
				type: String,
				default: '请输分析内容...'
			},
			height: {
				type: String,
				default: 'calc(var(--safe-height) - var(--navbar-height) - 96rpx)'
			}
		},
		data() {
			return {
				html: '<p><br></p>',
				editorFocus: false,
				editorCtx: null,
				tools: [
					{name: 'image', icon: 'tp', text: '插入图片'},
					{name: 'undo', icon: 'cx', text: '撤销'},
					{name: 'redo', icon: 'czcx', text: '恢复'},
					{name: 'fontSize', icon: 'zh', text: '设置字号', value: 14},
					{name: 'color', icon: 'ztys', text: '设置字体颜色', value: '#333333'},
					{name: 'backgroundColor', icon: 'ztbjys', text: '设置字体背景颜色', value: ''},
					{name: 'bold', icon: 'ztjc', text: '粗体'},
					{name: 'italic', icon: 'xt', text: '斜体'},
					{name: 'underline', icon: 'ztxhx', text: '下划线'},
					{name: 'align', icon: 'jzz', text: '左对齐', value: 'left'},
					{name: 'align', icon: 'jz', text: '居中对齐', value: 'center'},
					{name: 'align', icon: 'jy', text: '右对齐', value: 'right'}
				],
				currentTool: [],
				popupInfo: {},
				colorList: [
					'#333333','#666666','#999999','#CCCCCC','#FFFFFF',
					'#F23030','#FF8316','#FFC600','#FFEA00','#76CC3D',
					'#16D95F','#21D3D9','#4C88FF','#0055FF','#834CFF',
					'#E339E6','#F2248F','#FFB2B2','#FFE999','#AEE58A',
					'#99E5FF','#B899FF','#FD99FF','#D9C16C','#CCAD8F'
				]
			}
		},
		watch: {
			html(newValue) {
				if(!newValue || newValue == '<p><br></p>'){
					this.$emit('change', {complete: false, html: null})
				}else{
					let str = newValue.replace(/<[^<>]+>/g, "").replace(/&nbsp;/gi, "");
					if(str.length){
						this.$emit('change', {complete: true, html: newValue})
					}else{
						this.$emit('change', {complete: false, html: null})
					}
				}
			}
		},
		methods: {
			//编辑器准备完成
			onEditorReady() {
				uni.createSelectorQuery().select('#editor').context((res) => {
					this.editorCtx = res.context
					let newValue = uni.getStorageSync('article_'+this.type)
					if(newValue){
						let html = newValue.trim()
						//处理IOS多余Html代码
						if(newValue.includes('<body>') && newValue.includes('</body>')){
							html = newValue.match(/<body>[\s\S]*<\/body>/g)
							if(html){
								html = html[0].slice(6, -7).trim()
								if(/<\/span>/ig.test(html)){
									html = html.replace(/<span.*?>/ig, "");
									html = html.replace(/<\/span>/ig, "");
								}
							}
						}
						const reg = /^<[pP].*>/i;
						if(!reg.test(html)){
							//处理安卓图文兼容
							html = '<p>'+html+'</p>'
						}
						//初始化编辑器内容
						this.editorCtx.setContents({html})
						this.html = html
					}
					this.editorCtx.scrollIntoView()
				}).exec()
			},
			//编辑器聚焦
			onEditorFocus(e) {
				let {html, text, delta} = e.detail
				this.html = html
				this.editorFocus = true
				this.$emit('focus')
			},
			//编辑器失焦
			onEditorBlur(e) {
				let {html, text, delta} = e.detail
				this.html = html
				this.editorFocus = false
				this.$emit('blur')
			},
			//编辑器输入
			onEditorInput(e) {
				let {html, text, delta} = e.detail
				this.html = html
			},
			//设置编辑器使用的样式
			format(e) {
				let { index, name, value, label } = e.target.dataset
				if(name){
					console.log(name);
					if(name == 'image'){ //插入图片
						label = null
						this.chooseImg()
					}else if(name == 'undo' || name == 'redo'){ //撤销重做
						this.editorCtx[name]()
					}else if(name == 'fontSize'){ //字号
						this.editorCtx.blur()
						this.popupInfo = Object.assign({}, e.target.dataset)
						this.toggle(true)
						label = null
					}else if(name == 'color'){ // 字体颜色
						this.editorCtx.blur()
						this.popupInfo = Object.assign({}, e.target.dataset)
						this.toggle(true)
						label = null
					}else if(name == 'backgroundColor'){ //背景色
						this.editorCtx.blur()
						this.popupInfo = Object.assign({}, e.target.dataset)
						let colorTool = this.tools.find(item => item.name == 'color');
						this.popupInfo.color = colorTool.value
						this.toggle(true)
						label = null
					}else if(name == 'align'){ //居中居左居右
						this.editorCtx.format(name, value);
					}else{//其他样式设置
						let indexCurrent = this.currentTool.indexOf(name)
						if(indexCurrent > -1){
							this.currentTool.splice(indexCurrent)
							label = '取消' + label
						}else{
							this.currentTool.push(name)
						}
						this.editorCtx.format(name, value);
					}
					this.toast(label)
				}
			},
			//操作提示
			toast(label) {
				if(label){
					uni.showToast({
						duration: 500,
						icon: 'none',
						title: label
					});
				}
			},
			//选择图片
			chooseImg() {
				uni.chooseImage({
					count: 1,
					sizeType: ['compressed'],
					extension: ['jpg','png'],
					success: (res) => {
						console.log(res.tempFilePaths[0]);
						console.log(res.tempFiles[0]);
						this.editorCtx.insertImage({
							src: res.tempFilePaths[0],
							alt: '图片预览失败'
						});
					}
				});
			},
			//切换弹窗展示
			toggle(status){
				console.log(status);
				if(status){
					this.$refs.popup.open()
				}else{
					this.$refs.popup.close()
				}
			},
			//滑动回调
			sliderChange(e) {
				this.popupInfo.value = e.detail.value
			},
			//颜色选择回调
			colorChange(e) {
				console.log(e);
				this.popupInfo.value = e.target.dataset.color
			},
			//确定提交样式
			submitFormat() {
				console.log(this.popupInfo);
				let { name, value } = this.popupInfo
				console.log(name);
				console.log(value);
				if(name == 'fontSize'){
					this.editorCtx.format(name, value+'px');
				}else{
					this.editorCtx.format(name, value);
				}
				let index = this.popupInfo.index
				if(this.tools[index]){
					this.tools[index].value = value
				}
				console.log(this.tools[index]);
				this.$refs.popup.close()
			}
		}
	}
</script>

<style lang="scss" scoped>
	.content-editor{
		.editor-box{
			background-color: #fff;
			.editor-content{
				box-sizing: border-box;
				/deep/ .ql-container{
					//min-height: unset;
					.ql-blank::before{
						margin: 15rpx 0;
						font-style: normal;
						font-size: 28rpx;
						color: #B3B3B3;
					}
					.ql-editor{
						padding: 20rpx;
						font-size: 28rpx;
						line-height: 1.25;
						letter-spacing: 2rpx;
						word-break: break-all;
						overflow-x: hidden;
						user-select: none;
						-webkit-user-select: none;
						-ms-user-select: none;
						-moz-user-select: none;
						-webkit-touch-callout: none;
						body{
							margin: 0;
							padding: 0;
							color:#333333;
							background: #FFFFFF;
						}
						div, p {
							margin: 15rpx 0;
						}
						img{
							display: inline-block;
							max-width: 100% !important;
							height: auto !important;
							vertical-align: middle;
							margin: 10rpx 0;
							border-radius: 10rpx;
						}
					}
				}
			}
			.editor-tools{
				max-width: $max-width;
				margin: $pc-margin;
				background-color: #fff;
				position: fixed;
				bottom: 0;
				left: 0;
				right: 0;
				height: calc(96rpx + var(--safe-area-inset-bottom));
				padding-bottom: var(--safe-area-inset-bottom);
				border-top: 1rpx solid #EDEDED;
				box-sizing: border-box;
				justify-content: space-between;
				.icon{
					width: 48rpx;
					height: 48rpx;
				}
				.tools-list{
					flex: 2;
					position: relative;
					.scroll-view{
						width: 642rpx;
						white-space: nowrap;
						.list{
							width: 100%;
							.icon{
								margin: 0 22rpx;
								padding: 8rpx;
								&.active{
									background: #EDEDED;
								}
							}
							.icon:active{
								background: #EDEDED;
							}
						}
					}
					.mask{
						position: absolute;
						right: 0;
						width: 40rpx;
						height: 96rpx;
						background: linear-gradient(90deg, rgba(237,237,237,0) 0%, #EDEDED 100%);
					}
				}
				.keyboard{
					width: 108rpx;
				}
			}
		}
		.popup-box{
			z-index: 1000;
			/deep/ .bottom{
				max-width: $max-width;
				margin: $pc-margin;
			}
			.popup-head{
				height: 96rpx;
				padding: 0 20rpx;
				background-color: #FFFFFF;
				border-radius: 20rpx 20rpx 0rpx 0rpx;
				border-bottom: 1rpx solid #EDEDED;
				.text-bold{
					flex: 2;
					text-align: center;
					font-size: 36rpx;
				}
				.close-icon{
					width: 40rpx;
					height: 40rpx;
				}
			}
			.popup-view{
				padding: 0 30rpx;
				.display-area{
					margin-top: 30rpx;
					width: 100%;
					background: #FFFFFF;
					border: 1rpx solid #D9D9D9;
					border-radius: 10rpx;
				}
				.format-info{
					margin-top: 50rpx;
				}
				.font-size{
					height: 840rpx;
					padding-top: 40rpx;
					box-sizing: border-box;
					.display-area{
						height: 200rpx;
					}
					.slider-box{
						/deep/ .slider{
							margin: 30rpx 0 20rpx 0;
							.uni-slider-handle-wrapper{
								height: 12rpx;
							}
							.uni-slider-thumb{
								width: 48rpx !important;
								height: 48rpx !important;
								background: transparent url('~@/public/images/editor/jdgb.png') center center/48rpx 48rpx no-repeat;
							}
						}
					}
				}
				.font-color, .font-background{
					height: 840rpx;
					padding-top: 40rpx;
					box-sizing: border-box;
					.display-area{
						height: 96rpx;
					}
					.color-list{
						margin-top: 30rpx;
						flex-wrap: wrap;
						.color-item{
							margin-top: 10rpx;
							margin-right: 10rpx;
							width: 130rpx;
							height: 72rpx;
							background: #FFFFFF;
							border: 1px solid #D9D9D9;
							border-radius: 10rpx;
							box-sizing: border-box;
							.color-card{
								width: 108rpx;
								height: 50rpx;
								border-radius: 4rpx;
								border: 1px solid #EDEDED;
								box-sizing: border-box;
								pointer-events: none;
							}
							&.active{
								border: 2px solid #F23030;
							}
						}
						.color-item:nth-child(-n+5){
							margin-top: 0;
						}
						.color-item:nth-child(5n){
							margin-right: 0;
						}
					}
				}
				.font-background{
					.display-area{
						.bgcolor{
							padding: 10rpx;
						}
					}
					.color-box{
						margin-top: 30rpx;
						width: 100%;
						height: 72rpx;
						background: #FFFFFF;
						border: 1px solid #D9D9D9;
						border-radius: 10rpx;
						box-sizing: border-box;
						.text-regular{
							width: 668rpx;
							height: 50rpx;
							border-radius: 4rpx;
						}
					}
					.color-list{
						margin-top: 10rpx;
					}
				}
			}
			.bottom-ios{
				background-color: #fff;
			}
		}
	}
</style>